package streaming.test.session_transmission;

import java.awt.Component;
import java.io.IOException;
import java.net.InetAddress;

import javax.media.CannotRealizeException;
import javax.media.Manager;
import javax.media.NoPlayerException;
import javax.media.Player;
import javax.media.protocol.DataSource;
import javax.media.rtp.InvalidSessionAddressException;
import javax.media.rtp.ReceiveStream;
import javax.media.rtp.ReceiveStreamListener;
import javax.media.rtp.SessionAddress;
import javax.media.rtp.event.NewReceiveStreamEvent;
import javax.media.rtp.event.ReceiveStreamEvent;
import javax.media.rtp.rtcp.SourceDescription;

import streaming.test.session_transmission.StreamManager.State;

import com.sun.media.rtp.RTPSessionMgr;


public class Receiver implements StreamManager, ReceiveStreamListener{

	private RTPSessionMgr manager;
	private ReceiveStream stream;

	private DataSource dataSource;
	private Player player;

	private InetAddress source;
	private int port;
	private int localPort;
	
	private State state;

	public Receiver(InetAddress source, int port, int localPort) {
		this.source = source;
		this.port = port;
		this.localPort = localPort;
		this.state = State.NEW;
	}
	
	public Receiver() {
		
		this.state = State.NEW;
	}

	public void initialize(){

		try {

			manager = new RTPSessionMgr();

			manager.addReceiveStreamListener(this);

			String cname = manager.generateCNAME();
			SourceDescription[] userdesclist= new SourceDescription[]{
					new SourceDescription(SourceDescription
							.SOURCE_DESC_EMAIL,
							"jmf-user@sun.com",
							1,
							false),
					new SourceDescription(SourceDescription
							.SOURCE_DESC_CNAME,
							cname,
							1,
							false),
					new SourceDescription(SourceDescription
							.SOURCE_DESC_TOOL,
							"test multimedia streaminga",
							1,
							false)
            };
			// TODO uzeti port iz parametara
			manager.initSession(new SessionAddress(null, localPort), userdesclist, 0.05, 0.25);
//			manager.addTarget(new SessionAddress(source, port));

			manager.startSession(new SessionAddress(source, port), 16, null);
//			manager.addTarget(new SessionAddress(source, port));

		} catch (InvalidSessionAddressException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}

	}
	
	public Component getVisualComponent(){
		if(state == State.IN_PROGRESS){
			return player.getVisualComponent();
		}
		return null;
	}


	@Override
	public void pause() {
		if(state == State.IN_PROGRESS){
			player.stop();
			state = State.PAUSED;
		}
	}

	@Override
	public void start() {
		if(state == State.INITIALIZED || state == State.PAUSED){
			player.start();
			state = State.IN_PROGRESS;
		}

	}

	@Override
	public void stop() {
		if(state == State.IN_PROGRESS || state == State.PAUSED){
			player.stop();
			player.deallocate();
			state = State.ENDED;
		}

	}

	@Override
	public void update(ReceiveStreamEvent e) {
		if(e instanceof NewReceiveStreamEvent){
			
			try {
				stream = ((NewReceiveStreamEvent)e).getReceiveStream();
				player = Manager.createRealizedPlayer(stream.getDataSource());
			
				this.state = State.INITIALIZED;
				System.out.println(stream.getParticipant().toString());
				
				
			} catch (Exception e1) {
				this.state = State.FAILED;
				e1.printStackTrace();
			} 
			
		}
	}

	public InetAddress getSource() {
		return source;
	}

	public void setSource(InetAddress source) {
		this.source = source;
	}

	public int getPort() {
		return port;
	}

	public void setPort(int port) {
		this.port = port;
	}

}
